package ru.spb.osll.myfit.server.parser;

import static org.junit.Assert.assertEquals;

import java.util.List;

import org.apache.commons.lang.StringUtils;
import org.easymock.EasyMock;
import org.junit.Before;
import org.junit.Test;

import ru.spb.osll.myfit.common.Include;
import ru.spb.osll.myfit.common.PageElement;
import ru.spb.osll.myfit.common.PageElementType;
import ru.spb.osll.myfit.common.Table;
import ru.spb.osll.myfit.common.TableStyle;
import ru.spb.osll.myfit.common.WikiText;
import ru.spb.osll.myfit.server.Converter;
import ru.spb.osll.myfit.util.CollectionUtils;

public class NewPageParserTest {
  private final String LINE_SEPARATOR = System.getProperty("line.separator");
  private Converter converter;

  @Before
  public void setUp() {
    converter = EasyMock.createMock(Converter.class);
  }

  @Test
  public void testParsePage() {
    PageParserNew PageParserNew = new PageParserNew(converter);
    List<String> lines = CollectionUtils.list(
        "|enable advanced retention on clusters|", LINE_SEPARATOR,
        "|with cubetools|", "|write|10|files of size|10KB|using|10|threads|",
        LINE_SEPARATOR, "!include .TestPage");

    List<PageElement> elements = PageParserNew.parsePage(lines);
    assertEquals(3, elements.size());
    Table first = (Table) elements.get(0);
    Table second = (Table) elements.get(1);
    checkTables(first, second);
    Include include = (Include) elements.get(2);
    assertEquals(".TestPage", include.getPath());
  }

  @Test
  public void testWikiParser() {
    PageParserNew PageParserNew = new PageParserNew(converter);
    String wiki = "[[.Text]]";
    String html = "<a href=\".Text\">.Text</a>";
    EasyMock.expect(converter.convertWikiToHtml(wiki)).andReturn(html);
    EasyMock.replay(converter);

    List<PageElement> elements = PageParserNew.parsePage(CollectionUtils.list(
        "|enable advanced retention on clusters|", wiki, "|with cubetools|",
        "|write|10|files of size|10KB|using|10|threads|"));

    assertEquals(3, elements.size());
    assertEquals(PageElementType.TABLE, elements.get(0).getType());
    assertEquals(PageElementType.WIKI_TEXT, elements.get(1).getType());
    WikiText wikiText = (WikiText) elements.get(1);
    assertEquals(wiki, wikiText.getWikiText());
    assertEquals(html, wikiText.getHtmlText());
    EasyMock.verify(converter);

  }

  @Test
  public void testParsePageWithInclude1() {
    PageParserNew PageParserNew = new PageParserNew(converter);

    List<PageElement> elements = PageParserNew.parsePage(CollectionUtils.list(
        "|enable advanced retention on clusters|", LINE_SEPARATOR,LINE_SEPARATOR,
        "!include .TestPage", "|with cubetools|",
        "|write|10|files of size|10KB|using|10|threads|"));

    assertEquals(3, elements.size());
    assertEquals(PageElementType.INCLUDE.getKey(), elements.get(1).getType()
        .getKey());
    Include include = (Include) elements.get(1);
    assertEquals(".TestPage", include.getPath());
  }

  @Test
  public void testParsePageWithInclude2() {
    PageParserNew PageParserNew = new PageParserNew(converter);
    List<PageElement> elements = PageParserNew.parsePage(CollectionUtils.list(
        "|enable advanced retention on clusters|", LINE_SEPARATOR,"!include    .Test2Page   ",
        LINE_SEPARATOR, "|with cubetools|",
        "|write|10|files of size|10KB|using|10|threads|"));

    assertEquals(3, elements.size());
    assertEquals(PageElementType.INCLUDE.getKey(), elements.get(1).getType()
        .getKey());
    Include include = (Include) elements.get(1);
    assertEquals(".Test2Page", include.getPath());
  }

  private void checkTables(Table first, Table second) {
    assertEquals(TableStyle.UNKNOWN_FIXTURE, first.getStyle());
    assertEquals(1, first.getData().size());
    assertEquals(1, first.getData().get(0).size());
    assertEquals("enable advanced retention on clusters",
        StringUtils.join(first.getData().get(0), "|"));

    assertEquals(TableStyle.UNKNOWN_FIXTURE, second.getStyle());
    assertEquals(2, second.getData().size());
    assertEquals("with cubetools",
        StringUtils.join(second.getData().get(0), "|"));
    assertEquals("write|10|files of size|10KB|using|10|threads",
        StringUtils.join(second.getData().get(1), "|"));

  }
}
